/*******************************************************************************
 * Copyright (c) 2009 Dop Sun.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     Dop Sun - initial API and implementation
 ******************************************************************************/
package com.softao.ming.gde.internal.core.bootstrap;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.zip.ZipEntry;
import java.util.zip.ZipFile;

import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IConfigurationElement;
import org.eclipse.core.runtime.IExtension;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.pde.core.plugin.IPluginModelBase;
import org.eclipse.pde.core.plugin.PluginRegistry;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

import com.softao.ming.gde.internal.core.GdeCore;
import com.softao.ming.gde.internal.core.pde.PdeCoreUtil;
import com.softao.ming.gde.internal.core.util.XmlHelper;

/**
 * 
 */
public class BootstrapProduct {
	/** */
	public static final String DEFAULT_HTML_VERSION = "";
	/** */
	public static final String HTML_401_STRICT = "HTML 4.01 Strict DTD";
	/** */
	public static final String HTML_401_TRANSITIONAL = "HTML 4.01 Transitional DTD";
	/** */
	public static final String HTML_401_FRAMESET = "HTML 4.01 Frameset DTD";
	
	private String mUniqueIdentifier;
	private String mName;
	private BootstrapApplication mApplication;
	private String mHtmlVersion;
	
	/**
	 * @param args 
	 * @throws CoreException 
	 */
	public BootstrapProduct(BootstrapGeneratorArgs args) throws CoreException {
		boolean useProduct = args.isUseProduct();
		if (useProduct) {
			mUniqueIdentifier = args.getTargetId();
			IExtension[] extensions = PdeCoreUtil.findExtensions("com.softao.ming.gwt.core.runtime.products", true);
			for (IExtension extension : extensions) {
				IConfigurationElement[] elements = extension.getConfigurationElements();
				for (IConfigurationElement element : elements) {
					if (element.getAttribute("id").equals(mUniqueIdentifier)) {
						String nsId = extension.getNamespaceIdentifier();
						IPluginModelBase bundle = PluginRegistry.findModel(nsId);
						try {
							mHtmlVersion = resolveHtmlVersion(bundle);
						} catch (IOException e) {
							Status status = new Status(IStatus.ERROR, GdeCore.PLUGIN_ID, "Can not find the HTML version.");
							throw new CoreException(status);
						}
						
						String applicationId = element.getAttribute("application");
						mApplication = new BootstrapApplication(applicationId);
						mName = element.getAttribute("name");
					}
				}
			}
		} else {
			mUniqueIdentifier = null;
			String applicationId = args.getTargetId();
			mApplication = new BootstrapApplication(applicationId);
		}
	}

	private static final String resolveHtmlVersion(IPluginModelBase bundle) throws IOException {
		String installLocation = bundle.getInstallLocation();
		File file = new File(installLocation);
		if (file.isFile()) {
			ZipFile zipFile = new ZipFile(file, ZipFile.OPEN_READ);
			ZipEntry gwtPluginEntry = zipFile.getEntry("gwt.plugin.xml");
			if (gwtPluginEntry != null) {
				InputStream inputStream = zipFile.getInputStream(gwtPluginEntry);
				try {
					return readHtmlVersionFromInputStream(inputStream);
				} finally {
					inputStream.close();
				}
			}
			zipFile.close();
		} else {
			File gwtPluginFile = new File(file, "gwt.plugin.xml");
			if (gwtPluginFile != null) {
				InputStream inputStream = new FileInputStream(gwtPluginFile);
				try {
					return readHtmlVersionFromInputStream(inputStream);
				} finally {
					inputStream.close();
				}
			}
		}
		
		return DEFAULT_HTML_VERSION;
	}
	
	private static final String readHtmlVersionFromInputStream(InputStream inputStream) throws IOException {
		Document document = XmlHelper.loadDocument(inputStream);
		Element root = document.getDocumentElement();
		String readOcc = XmlHelper.readOcc(root, "html.version");
		return readOcc != null ? readOcc : DEFAULT_HTML_VERSION;
	}
	
	/**
	 * @return the uniqueIdentifier
	 */
	public String getUniqueIdentifier() {
		return mUniqueIdentifier;
	}
	
	/**
	 * @return the application
	 */
	public BootstrapApplication getApplication() {
		return mApplication;
	}
	
	/**
	 * @return the name
	 */
	public String getName() {
		return mName;
	}
	
	/**
	 * @return the htmlVersion
	 */
	public String getHtmlVersion() {
		return mHtmlVersion;
	}
}
